var proto_tool=require("./protocol_tool");

var log={
	info:console.log,
	warn:console.log,
	error:console.log,
};

var protocol = {
    PROTO_JSON: 1,  //json协议,字符串
    PROTO_BYTE: 2,  //二进制协议

    encode:encode,
    decode:decode,

    register_encoder:register_encoder,
    register_decoder:register_decoder
};

//编码表中保存所有的编码函数
var encoder_table={};

//解码表中保存所有的解码函数
var decoder_table={};


function get_key(stype,ctype){
	return stype*65536+ctype;
}

//加密
function encrypt(cmd){
	return cmd;
}

//解密
function decrypt(cmd){
	return cmd;
}


//编码
//协议类型,服务号,命令号,用户标识,编码,二进制/字符串,body:[数据]
function encode(proto_type,stype,ctype,body){

	var buf=new ArrayBuffer(10);
	var dataview=new DataView(buf);

	dataview.setUint16(0,stype);
	dataview.setUint16(2,ctype);
	dataview.setUint32(4,0);
	dataview.setUint16(8,proto_type);

	if (body==null){
		return encrypt(buf);
	}

    if (proto_type == protocol.PROTO_JSON) {

    	var json_str=JSON.stringify(body);
    	var json_buf=null;
    	json_buf=proto_tool.add_str16(json_buf,json_str);

    	return encrypt(ArrayBuffer.concat([buf,json_buf]));
	}
	else{

		var key=get_key(stype,ctype);
		if (!encoder_table[key])
			return null;

		//字节流加密
		return encrypt(ArrayBuffer.concat([buf,encoder_table[key](body)]));
	}

	return null;
}

//解码
//协议类型,二进制/字符串,body:[服务号,命令号,数据]
function decode(proto_type,body){

	var decrypt_body=decrypt(body);

	if (decrypt_body.byteLength<10)
		return null;

	var dataview=new DataView(decrypt_body);
	var stype=dataview.getUint16(0);
	var ctype=dataview.getUint16(2);

	if (decrypt_body.byteLength==10){
		return {0:stype,1:ctype,2:null};
	}


    if (proto_type == protocol.PROTO_JSON) {

    	var json_len=dataview.getUint16(10);
		var obj={
    		0:stype,
    		1:ctype,
    		2:JSON.parse(dataview.read_utf8(12,json_len))
    	};

		return obj;
	}
	else{
		
		var key=get_key(stype,ctype);
		if (!decoder_table[key])
			return null;

		var obj={
			0:stype,
			1:ctype,
			2:decoder_table[key](decrypt_body.slice(10))
		};

		return obj;
	}
	return null;
}


function register_encoder(stype,ctype,func){
	var key=get_key(stype,ctype);
	if (encoder_table[key])
		log.warn("stype:"+stype+" ctype:"+ctype+"已经注册了");

	encoder_table[key]=func;
}

function register_decoder(stype,ctype,func){
	var key=get_key(stype,ctype);
	if (decoder_table[key])
		log.warn("stype:"+stype+" ctype:"+ctype+"已经注册了");

	decoder_table[key]=func;
}


module.exports=protocol;